NORM
Overview
The NORM function provides comprehensive access to the normal (Gaussian) distribution, the most fundamental continuous probability distribution in statistics. It computes various statistical measures including probability density, cumulative probabilities, quantiles, and distribution moments using SciPy’s scipy.stats.norm implementation.
The normal distribution, also known as the Gaussian distribution or bell curve, is characterized by two parameters: the mean (\mu, specified by loc) which determines the center of the distribution, and the standard deviation (\sigma, specified by scale) which controls the spread. The probability density function (PDF) is defined as:
f(x) = \frac{1}{\sigma\sqrt{2\pi}} \exp\left(-\frac{(x-\mu)^2}{2\sigma^2}\right)
This function supports multiple calculation methods through the norm_method parameter:
- PDF: Probability density function—returns the height of the probability curve at a given point x
- CDF: Cumulative distribution function—returns P(X \leq x), the probability that a random variable is less than or equal to x
- ICDF: Inverse CDF (percent point function)—returns the value x such that P(X \leq x) = q for a given probability q
- SF: Survival function—returns P(X > x) = 1 - \text{CDF}(x), sometimes more accurate than computing 1 - \text{CDF} directly
- ISF: Inverse survival function—returns the value x for a given survival probability
- Mean/Median/Var/Std: Returns the distribution’s mean, median, variance, or standard deviation
The normal distribution is central to statistical inference due to the Central Limit Theorem, which states that the sum of many independent random variables tends toward a normal distribution. This makes it essential for hypothesis testing, confidence intervals, quality control, and financial modeling. For more information, see the SciPy statistics documentation and the SciPy GitHub repository.
This example function is provided as-is without any representation of accuracy.
Excel Usage
=NORM(value, loc, scale, norm_method)
value(float, optional, default: null): Input value x for pdf/cdf/sf, or probability q for icdf/isf (0-1). Not required for mean/median/var/std.loc(float, optional, default: 0): Mean of the distribution.scale(float, optional, default: 1): Standard deviation of the distribution (must be > 0).norm_method(str, optional, default: “pdf”): Method to compute.
Returns (float): Result of the requested method, or str error message if input is invalid.
Examples
Example 1: PDF at x=0 for standard normal
Inputs:
| value | loc | scale | norm_method |
|---|---|---|---|
| 0 | 0 | 1 |
Excel formula:
=NORM(0, 0, 1, "pdf")
Expected output:
0.3989
Example 2: CDF at x=1 for standard normal
Inputs:
| value | loc | scale | norm_method |
|---|---|---|---|
| 1 | 0 | 1 | cdf |
Excel formula:
=NORM(1, 0, 1, "cdf")
Expected output:
0.8413
Example 3: Inverse CDF (quantile) at q=0.841345
Inputs:
| value | loc | scale | norm_method |
|---|---|---|---|
| 0.841345 | 0 | 1 | icdf |
Excel formula:
=NORM(0.841345, 0, 1, "icdf")
Expected output:
1
Example 4: Mean of standard normal distribution
Inputs:
| loc | scale | norm_method |
|---|---|---|
| 0 | 1 | mean |
Excel formula:
=NORM(0, 1, "mean")
Expected output:
0
Example 5: Survival function at x=1 for standard normal
Inputs:
| value | loc | scale | norm_method |
|---|---|---|---|
| 1 | 0 | 1 | sf |
Excel formula:
=NORM(1, 0, 1, "sf")
Expected output:
0.1587
Example 6: Variance of normal with scale=2
Inputs:
| loc | scale | norm_method |
|---|---|---|
| 5 | 2 | var |
Excel formula:
=NORM(5, 2, "var")
Expected output:
4
Python Code
from scipy.stats import norm as scipy_norm
import math
def norm(value=None, loc=0, scale=1, norm_method='pdf'):
"""
Normal (Gaussian) distribution function supporting multiple methods.
See: https://docs.scipy.org/doc/scipy/reference/generated/scipy.stats.norm.html
This example function is provided as-is without any representation of accuracy.
Args:
value (float, optional): Input value x for pdf/cdf/sf, or probability q for icdf/isf (0-1). Not required for mean/median/var/std. Default is None.
loc (float, optional): Mean of the distribution. Default is 0.
scale (float, optional): Standard deviation of the distribution (must be > 0). Default is 1.
norm_method (str, optional): Method to compute. Valid options: PDF, CDF, ICDF, SF, ISF, Mean, Median, Var, Std. Default is 'pdf'.
Returns:
float: Result of the requested method, or str error message if input is invalid.
"""
valid_methods = {'pdf', 'cdf', 'icdf', 'sf', 'isf', 'mean', 'median', 'var', 'std'}
if not isinstance(norm_method, str):
return f"Invalid method: {norm_method}. Must be a string."
norm_method = norm_method.lower()
if norm_method not in valid_methods:
return f"Invalid method: {norm_method}. Must be one of {', '.join(sorted(valid_methods))}."
try:
loc = float(loc)
scale = float(scale)
except (ValueError, TypeError):
return "Invalid input: loc and scale must be numbers."
if scale <= 0:
return "Invalid input: scale must be > 0."
# Methods that require 'value'
value_methods = {'pdf', 'cdf', 'icdf', 'sf', 'isf'}
if norm_method in value_methods:
if value is None:
return f"Invalid input: missing required argument 'value' for method '{norm_method}'."
try:
value = float(value)
except (ValueError, TypeError):
return "Invalid input: value must be a number."
if norm_method in {'icdf', 'isf'} and not (0 <= value <= 1):
return f"Invalid input: value (probability) must be between 0 and 1 for {norm_method}."
try:
dist = scipy_norm(loc, scale)
if norm_method == 'pdf':
result = dist.pdf(value)
elif norm_method == 'cdf':
result = dist.cdf(value)
elif norm_method == 'sf':
result = dist.sf(value)
elif norm_method == 'icdf':
result = dist.ppf(value)
elif norm_method == 'isf':
result = dist.isf(value)
elif norm_method == 'mean':
result = dist.mean()
elif norm_method == 'median':
result = dist.median()
elif norm_method == 'var':
result = dist.var()
elif norm_method == 'std':
result = dist.std()
else:
return f"Internal error: method {norm_method} not implemented."
except Exception as e:
return f"scipy.stats.norm error: {str(e)}"
# Handle NaN and Inf
# Check if result is a number (float or numpy scalar)
try:
result_float = float(result)
except (ValueError, TypeError):
return f"Result is not a number: {result}"
if math.isnan(result_float):
return "Result is NaN (not a number)"
if math.isinf(result_float):
return "inf" if result_float > 0 else "-inf"
return result_float